package com.heima.article.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.heima.api.behavior.IBehaviorClient;
import com.heima.api.user.IUserClient;
import com.heima.article.mapper.ApCollectionMapper;
import com.heima.article.service.IApCollectionService;
import com.heima.common.exception.CustomException;
import com.heima.model.article.dtos.ArticleInfoDto;
import com.heima.model.article.dtos.CollectionBehaviorDto;
import com.heima.model.article.pojos.ApCollection;
import com.heima.model.article.vos.ArticleBehaviorVo;
import com.heima.model.common.dtos.ResponseResult;
import com.heima.model.common.enums.AppHttpCodeEnum;
import com.heima.utils.common.UserThreadLocal;
import com.heima.utils.common.WmThreadLocalUtil;
import org.springframework.beans.BeanUtils;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.data.redis.core.ValueOperations;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.time.LocalDateTime;
import java.time.ZoneId;
import java.util.ArrayList;
import java.util.Date;
import java.util.concurrent.TimeUnit;

/**
 * <p>
 * APP收藏信息表 服务实现类
 * </p>
 *
 * @author fkn
 * @since 2024-08-21
 */
@Service
public class ApCollectionServiceImpl extends ServiceImpl<ApCollectionMapper, ApCollection> implements IApCollectionService {

    @Resource
    private ApCollectionMapper collectionMapper;

    @Resource
    private IUserClient iUserClient;

    @Resource
    private IBehaviorClient iBehaviorClient;

    @Resource
    private StringRedisTemplate stringRedisTemplate;

    private final static String COLLECTION = "COLLECTION";
    private final static String NOT_COLLECTION = "NOT_COLLECTION";

    @Override
    public void collection(CollectionBehaviorDto dto) {
        ValueOperations<String, String> operation = stringRedisTemplate.opsForValue();
        //获取当前用户ID
        Integer userId = UserThreadLocal.get();
        //幂等性
        if (!operation.setIfAbsent(COLLECTION + userId,"1",1, TimeUnit.SECONDS)){
            throw new CustomException(AppHttpCodeEnum.NOT_REPETITION_OPERATION);
        }
        ApCollection apCollection = new ApCollection();
        BeanUtils.copyProperties(dto,apCollection);
        apCollection.setCollectionTime(LocalDateTime.now());
        apCollection.setUserId(UserThreadLocal.get());
        LocalDateTime publishTime = LocalDateTime.ofInstant(dto.getPublishedTime().toInstant(), ZoneId.systemDefault());

        apCollection.setPublishedTime(publishTime);

        collectionMapper.insert(apCollection);
    }

    @Override
    public void cancelCollection(CollectionBehaviorDto dto) {
        ValueOperations<String, String> operation = stringRedisTemplate.opsForValue();
        //获取当前用户ID
        Integer userId = UserThreadLocal.get();
        //幂等性
        if (!operation.setIfAbsent(NOT_COLLECTION + userId,"1",1, TimeUnit.SECONDS)){
            throw new CustomException(AppHttpCodeEnum.NOT_REPETITION_OPERATION);
        }
        if (null == dto.getEntryId()){
            throw new CustomException(AppHttpCodeEnum.ARTICLEID_IS_EMPTY);
        }
        LambdaQueryWrapper<ApCollection> condition = new LambdaQueryWrapper<ApCollection>()
                .eq(ApCollection::getEntryId, dto.getEntryId())
                .eq(ApCollection::getUserId, UserThreadLocal.get());
        collectionMapper.delete(condition);
    }

    @Override
    //@GlobalTransactional
    public ResponseResult loadArticleBehavior(ArticleInfoDto dto) {
        Integer userId = UserThreadLocal.get();
        int authorId = dto.getAuthorId();
        LambdaQueryWrapper<ApCollection> collectionCondition = new LambdaQueryWrapper<ApCollection>()
                .eq(ApCollection::getUserId, userId)
                .eq(ApCollection::getEntryId, dto.getArticleId());
        ApCollection one = getOne(collectionCondition);
        ArticleBehaviorVo articleBehaviorVo = new ArticleBehaviorVo();
        articleBehaviorVo.setCollection(one != null);

        ArrayList<Integer> list = new ArrayList<>();
        list.add(userId);
        list.add(authorId);
        ResponseResult follow = iUserClient.isFollow(list);
        Boolean isFollow = (Boolean) follow.getData();
        articleBehaviorVo.setFollow(isFollow);

        ArrayList<Object> ids = new ArrayList<>();
        ids.add(userId);
        ids.add(dto.getArticleId());
        ArrayList<Boolean> booleans = (ArrayList<Boolean>) iBehaviorClient.likeAndUnlike(ids).getData();
        articleBehaviorVo.setLike(booleans.get(0));
        articleBehaviorVo.setUnlike(booleans.get(1));
        return ResponseResult.okResult(articleBehaviorVo);
    }
}
